#include <iostream>
#include <memory>


class Fruit{
public:
    virtual void name() = 0;
};

class Apple:public Fruit
{
public:
    void name() override{
        std::cout << "我是抽象工厂的苹果！" << std::endl;
    }
};

class Banana : public Fruit{
public:
    void name() override{
        std::cout << "我是抽象工厂的香蕉！" << std::endl;
    }
};

class Animal
{
public:
    virtual void name() = 0;
};

class Dog : public Animal
{
public:
    void name() override
    {
        std::cout << "我是抽象工厂的小狗！" << std::endl;
    }
};

class Lamp : public Animal
{
public:
    void name() override
    {
        std::cout << "我是抽象工厂的山羊！" << std::endl;
    }
};


class Factory
{
public:
    virtual std::shared_ptr<Fruit> getFruit(const std::string& name) = 0;
    virtual std::shared_ptr<Animal> getAnimal(const std::string& name) = 0;

};
//简单工厂模式
// class FruitFactory{
// public:
//     static std::shared_ptr<Fruit> create(const std::string& name)
//     {
//         if(name == "苹果")
//         {
//            return std::make_shared<Apple>();
//         }else{
//            return std::make_shared<Banana>();
//         }
//     }
// };

class AnimalFactory : public Factory
{
public:
    std::shared_ptr<Fruit> getFruit(const std::string& name)
    {
        return std::shared_ptr<Fruit>();
    }

    std::shared_ptr<Animal> getAnimal(const std::string& name)
    {
        if(name == "小狗")
        {
            return std::make_shared<Dog>();
        }
        else
        {
            return std::make_shared<Lamp>();
        }
    }
};

class FruitFactory : public Factory{
public:
    std::shared_ptr<Fruit> getFruit(const std::string& name)
    {
        if(name == "苹果")
        {
           return std::make_shared<Apple>();
        }else{
           return std::make_shared<Banana>();
        }
    }

    std::shared_ptr<Animal> getAnimal(const std::string& name)
    {
        return std::shared_ptr<Animal>();
    }
};

class FactoryProducer
{
public:
    static std::shared_ptr<Factory> create(const std::string& name)
    {
        if(name == "水果")
        {
            return std::make_shared<FruitFactory>();
        }
        else 
        {
            return std::make_shared<AnimalFactory>();
        }
    }
};


//工厂方法模式
// class FruitFactory{
// public:
//     virtual std::shared_ptr<Fruit> create() = 0;
    
// };

// class AppleFactory : public FruitFactory{
//     std::shared_ptr<Fruit> create() override{
//         std::cout << "苹果工厂产出一个苹果！" << std::endl;
//         return std::shared_ptr<Apple>();
//     }
// };

// class BananaFactory : public FruitFactory{
//     std::shared_ptr<Fruit> create() override{
//         std::cout << "香蕉工厂产出一个香蕉！" << std::endl;
//         return std::shared_ptr<Banana>();
//     }
// };

int main()
{
    // std::shared_ptr<Fruit> apple = FruitFactory::create("苹果");
    // apple->name();
    // std::shared_ptr<Fruit> banana = FruitFactory::create("香蕉");
    // banana->name();

    // std::shared_ptr<FruitFactory> ff(new AppleFactory());
    // std::shared_ptr<Fruit> apple = ff->create();
    // ff.reset(new BananaFactory());
    // std::shared_ptr<Fruit> banana = ff->create();


    std::shared_ptr<Factory> FF = FactoryProducer::create("水果");
    std::shared_ptr<Fruit> ff = FF->getFruit("苹果");
    ff->name();
    ff = FF->getFruit("香蕉");
    ff->name();

    std::shared_ptr<Factory> FA = FactoryProducer::create("动物");
    std::shared_ptr<Animal> fa = FA->getAnimal("小狗");
    fa->name();
    fa = FA->getAnimal("山羊");
    fa->name();

    return 0;
}